{
 "cells": [
  {
   "cell_type": "code",
   "execution_count": 3,
   "id": "eeea1f78",
   "metadata": {},
   "outputs": [],
   "source": [
    "import instructor\n",
    "from openai import OpenAI\n",
    "\n",
    "# Instantiate the client\n",
    "together_client = OpenAI(\n",
    "    base_url=f\"http://192.168.202.128:3000/v1\",\n",
    "    api_key=\"sk-dlrRsAGoZm2IesTN181876Bc78Dc495dB97fB77bF62366D7\",\n",
    ")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "id": "7ba7c7b0",
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "\"Hello! How can I assist you today? Whether it's providing information on a specific topic, helping with a task, or just having a chat, feel free to ask me anything or let's have a conversation.\""
      ]
     },
     "execution_count": 4,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "response = together_client.chat.completions.create(\n",
    "    model='qwen2.5:3b',\n",
    "    messages = [{\n",
    "        \"role\": \"user\", \n",
    "        \"content\": 'sup'\n",
    "    }]\n",
    ")\n",
    "\n",
    "response.choices[0].message.content"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 18,
   "id": "e0ba8258",
   "metadata": {},
   "outputs": [],
   "source": [
    "# Wrap together with the instructor client\n",
    "instructor_client = instructor.from_openai(together_client, mode=instructor.Mode.PARALLEL_TOOLS)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 19,
   "id": "b36c85f2",
   "metadata": {},
   "outputs": [],
   "source": [
    "from pydantic import BaseModel\n",
    "\n",
    "class Greeting(BaseModel):\n",
    "    hello: str"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 24,
   "id": "a2843154",
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List, Iterable\n",
    "\n",
    "response = instructor_client.chat.completions.create(\n",
    "    model='qwen2.5:3b',\n",
    "    messages = [{\n",
    "        \"role\": \"user\", \n",
    "        \"content\": 'sup'\n",
    "    }], \n",
    "    # Note: OpenAI uses response_format, instructor\n",
    "    #       uses response_model!\n",
    "    response_model=Iterable[Greeting]\n",
    ")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 30,
   "id": "43c60733",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "<generator object ParallelBase.from_response at 0x000001F10C51E8C0>\n"
     ]
    }
   ],
   "source": [
    "print(response)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 12,
   "id": "db5f7583",
   "metadata": {},
   "outputs": [],
   "source": [
    "from pydantic import Field\n",
    "from datetime import date\n",
    "from typing import List\n",
    "\n",
    "# Person only has a name, but we can easily extend it with other fields\n",
    "class Person(BaseModel):\n",
    "    name: str\n",
    "\n",
    "class CalendarEvent(BaseModel):\n",
    "    name: str\n",
    "    \n",
    "    # not supported by OpenAI. We want a format like 2025-01-30\n",
    "    date: date \n",
    "    participants: List[Person]\n",
    "\n",
    "    address_number: str\n",
    "    street_name: str\n",
    "    city_name: str\n",
    "\n",
    "    # Inline regex patterns not supported by OpenAI restrict state code \n",
    "    # to be two capital letters (OpenAI does not support pattern fields)\n",
    "    state_code: str = Field(pattern=r'[A-Z]{2}')\n",
    "\n",
    "    # Zip code must be five digits\n",
    "    zip_code: str = Field(pattern=r'\\d{5}') \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 13,
   "id": "078d707a",
   "metadata": {},
   "outputs": [],
   "source": [
    "event_description = \"\"\"\n",
    "Alice and Bob are going to a science fair on Friday, January 2024.\n",
    "The science fair is hosted at the gymnasium of Hazeldale Elementary\n",
    "School at 20080 SW Farmington Road in Beaverton Oregon.\n",
    "\"\"\""
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 15,
   "id": "5710ff8d",
   "metadata": {},
   "outputs": [],
   "source": [
    "def generate(\n",
    "    response_model, \n",
    "    user_prompt, \n",
    "    system_prompt=\"You are a helpful assistant.\",\n",
    "    model=\"qwen2.5:3b\",\n",
    "    # Can use 70b for a higher-quality model\n",
    "    # model=\"meta-llama/Meta-Llama-3.1-70B-Instruct-Turbo\",\n",
    "    max_retries=3,\n",
    "):\n",
    "    event = instructor_client.chat.completions.create(\n",
    "        model=model,\n",
    "        messages=[\n",
    "            {\"role\": \"system\", \"content\": system_prompt},\n",
    "            {\"role\": \"user\", \"content\": user_prompt\n",
    "            },\n",
    "        ],\n",
    "        response_model=response_model,\n",
    "        max_retries=max_retries\n",
    "    )\n",
    "\n",
    "    return event"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 16,
   "id": "17249494",
   "metadata": {},
   "outputs": [
    {
     "ename": "InstructorRetryException",
     "evalue": "Instructor does not support multiple tool calls, use List[Model] instead",
     "output_type": "error",
     "traceback": [
      "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m",
      "\u001b[1;31mAssertionError\u001b[0m                            Traceback (most recent call last)",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\instructor\\retry.py:174\u001b[0m, in \u001b[0;36mretry_sync\u001b[1;34m(func, response_model, args, kwargs, context, max_retries, strict, mode, hooks)\u001b[0m\n\u001b[0;32m    170\u001b[0m     response \u001b[38;5;241m=\u001b[39m update_total_usage(\n\u001b[0;32m    171\u001b[0m         response\u001b[38;5;241m=\u001b[39mresponse, total_usage\u001b[38;5;241m=\u001b[39mtotal_usage\n\u001b[0;32m    172\u001b[0m     )\n\u001b[1;32m--> 174\u001b[0m     \u001b[38;5;28;01mreturn\u001b[39;00m process_response(  \u001b[38;5;66;03m# type: ignore\u001b[39;00m\n\u001b[0;32m    175\u001b[0m         response\u001b[38;5;241m=\u001b[39mresponse,\n\u001b[0;32m    176\u001b[0m         response_model\u001b[38;5;241m=\u001b[39mresponse_model,\n\u001b[0;32m    177\u001b[0m         validation_context\u001b[38;5;241m=\u001b[39mcontext,\n\u001b[0;32m    178\u001b[0m         strict\u001b[38;5;241m=\u001b[39mstrict,\n\u001b[0;32m    179\u001b[0m         mode\u001b[38;5;241m=\u001b[39mmode,\n\u001b[0;32m    180\u001b[0m         stream\u001b[38;5;241m=\u001b[39mstream,\n\u001b[0;32m    181\u001b[0m     )\n\u001b[0;32m    182\u001b[0m \u001b[38;5;28;01mexcept\u001b[39;00m (ValidationError, JSONDecodeError) \u001b[38;5;28;01mas\u001b[39;00m e:\n",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\instructor\\process_response.py:172\u001b[0m, in \u001b[0;36mprocess_response\u001b[1;34m(response, response_model, stream, validation_context, strict, mode)\u001b[0m\n\u001b[0;32m    170\u001b[0m     \u001b[38;5;28;01mreturn\u001b[39;00m model\n\u001b[1;32m--> 172\u001b[0m model \u001b[38;5;241m=\u001b[39m response_model\u001b[38;5;241m.\u001b[39mfrom_response(\n\u001b[0;32m    173\u001b[0m     response,\n\u001b[0;32m    174\u001b[0m     validation_context\u001b[38;5;241m=\u001b[39mvalidation_context,\n\u001b[0;32m    175\u001b[0m     strict\u001b[38;5;241m=\u001b[39mstrict,\n\u001b[0;32m    176\u001b[0m     mode\u001b[38;5;241m=\u001b[39mmode,\n\u001b[0;32m    177\u001b[0m )\n\u001b[0;32m    179\u001b[0m \u001b[38;5;66;03m# ? This really hints at the fact that we need a better way of\u001b[39;00m\n\u001b[0;32m    180\u001b[0m \u001b[38;5;66;03m# ? attaching usage data and the raw response to the model we return.\u001b[39;00m\n",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\instructor\\function_calls.py:258\u001b[0m, in \u001b[0;36mOpenAISchema.from_response\u001b[1;34m(cls, completion, validation_context, strict, mode)\u001b[0m\n\u001b[0;32m    251\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m mode \u001b[38;5;129;01min\u001b[39;00m {\n\u001b[0;32m    252\u001b[0m     Mode\u001b[38;5;241m.\u001b[39mTOOLS,\n\u001b[0;32m    253\u001b[0m     Mode\u001b[38;5;241m.\u001b[39mMISTRAL_TOOLS,\n\u001b[1;32m   (...)\u001b[0m\n\u001b[0;32m    256\u001b[0m     Mode\u001b[38;5;241m.\u001b[39mFIREWORKS_TOOLS,\n\u001b[0;32m    257\u001b[0m }:\n\u001b[1;32m--> 258\u001b[0m     \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28mcls\u001b[39m\u001b[38;5;241m.\u001b[39mparse_tools(completion, validation_context, strict)\n\u001b[0;32m    260\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m mode \u001b[38;5;129;01min\u001b[39;00m {\n\u001b[0;32m    261\u001b[0m     Mode\u001b[38;5;241m.\u001b[39mJSON,\n\u001b[0;32m    262\u001b[0m     Mode\u001b[38;5;241m.\u001b[39mJSON_SCHEMA,\n\u001b[1;32m   (...)\u001b[0m\n\u001b[0;32m    268\u001b[0m     Mode\u001b[38;5;241m.\u001b[39mOPENROUTER_STRUCTURED_OUTPUTS,\n\u001b[0;32m    269\u001b[0m }:\n",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\instructor\\function_calls.py:523\u001b[0m, in \u001b[0;36mOpenAISchema.parse_tools\u001b[1;34m(cls, completion, validation_context, strict)\u001b[0m\n\u001b[0;32m    519\u001b[0m     \u001b[38;5;28;01massert\u001b[39;00m (\n\u001b[0;32m    520\u001b[0m         message\u001b[38;5;241m.\u001b[39mrefusal \u001b[38;5;129;01mis\u001b[39;00m \u001b[38;5;28;01mNone\u001b[39;00m\n\u001b[0;32m    521\u001b[0m     ), \u001b[38;5;124mf\u001b[39m\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mUnable to generate a response due to \u001b[39m\u001b[38;5;132;01m{\u001b[39;00mmessage\u001b[38;5;241m.\u001b[39mrefusal\u001b[38;5;132;01m}\u001b[39;00m\u001b[38;5;124m\"\u001b[39m\n\u001b[0;32m    522\u001b[0m \u001b[38;5;28;01massert\u001b[39;00m (\n\u001b[1;32m--> 523\u001b[0m     \u001b[38;5;28mlen\u001b[39m(message\u001b[38;5;241m.\u001b[39mtool_calls \u001b[38;5;129;01mor\u001b[39;00m []) \u001b[38;5;241m==\u001b[39m \u001b[38;5;241m1\u001b[39m\n\u001b[0;32m    524\u001b[0m ), \u001b[38;5;124mf\u001b[39m\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mInstructor does not support multiple tool calls, use List[Model] instead\u001b[39m\u001b[38;5;124m\"\u001b[39m\n\u001b[0;32m    525\u001b[0m tool_call \u001b[38;5;241m=\u001b[39m message\u001b[38;5;241m.\u001b[39mtool_calls[\u001b[38;5;241m0\u001b[39m]  \u001b[38;5;66;03m# type: ignore\u001b[39;00m\n",
      "\u001b[1;31mAssertionError\u001b[0m: Instructor does not support multiple tool calls, use List[Model] instead",
      "\nThe above exception was the direct cause of the following exception:\n",
      "\u001b[1;31mRetryError\u001b[0m                                Traceback (most recent call last)",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\instructor\\retry.py:163\u001b[0m, in \u001b[0;36mretry_sync\u001b[1;34m(func, response_model, args, kwargs, context, max_retries, strict, mode, hooks)\u001b[0m\n\u001b[0;32m    162\u001b[0m response \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;01mNone\u001b[39;00m\n\u001b[1;32m--> 163\u001b[0m \u001b[38;5;28;01mfor\u001b[39;00m attempt \u001b[38;5;129;01min\u001b[39;00m max_retries:\n\u001b[0;32m    164\u001b[0m     \u001b[38;5;28;01mwith\u001b[39;00m attempt:\n",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\tenacity\\__init__.py:443\u001b[0m, in \u001b[0;36mBaseRetrying.__iter__\u001b[1;34m(self)\u001b[0m\n\u001b[0;32m    442\u001b[0m \u001b[38;5;28;01mwhile\u001b[39;00m \u001b[38;5;28;01mTrue\u001b[39;00m:\n\u001b[1;32m--> 443\u001b[0m     do \u001b[38;5;241m=\u001b[39m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39miter(retry_state\u001b[38;5;241m=\u001b[39mretry_state)\n\u001b[0;32m    444\u001b[0m     \u001b[38;5;28;01mif\u001b[39;00m \u001b[38;5;28misinstance\u001b[39m(do, DoAttempt):\n",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\tenacity\\__init__.py:376\u001b[0m, in \u001b[0;36mBaseRetrying.iter\u001b[1;34m(self, retry_state)\u001b[0m\n\u001b[0;32m    375\u001b[0m \u001b[38;5;28;01mfor\u001b[39;00m action \u001b[38;5;129;01min\u001b[39;00m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39miter_state\u001b[38;5;241m.\u001b[39mactions:\n\u001b[1;32m--> 376\u001b[0m     result \u001b[38;5;241m=\u001b[39m action(retry_state)\n\u001b[0;32m    377\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m result\n",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\tenacity\\__init__.py:419\u001b[0m, in \u001b[0;36mBaseRetrying._post_stop_check_actions.<locals>.exc_check\u001b[1;34m(rs)\u001b[0m\n\u001b[0;32m    418\u001b[0m     \u001b[38;5;28;01mraise\u001b[39;00m retry_exc\u001b[38;5;241m.\u001b[39mreraise()\n\u001b[1;32m--> 419\u001b[0m \u001b[38;5;28;01mraise\u001b[39;00m retry_exc \u001b[38;5;28;01mfrom\u001b[39;00m \u001b[38;5;21;01mfut\u001b[39;00m\u001b[38;5;21;01m.\u001b[39;00m\u001b[38;5;21;01mexception\u001b[39;00m()\n",
      "\u001b[1;31mRetryError\u001b[0m: RetryError[<Future at 0x1f10c49fdd0 state=finished raised AssertionError>]",
      "\nThe above exception was the direct cause of the following exception:\n",
      "\u001b[1;31mInstructorRetryException\u001b[0m                  Traceback (most recent call last)",
      "Cell \u001b[1;32mIn[16], line 9\u001b[0m\n\u001b[0;32m      1\u001b[0m system_prompt \u001b[38;5;241m=\u001b[39m \u001b[38;5;124m\"\"\"\u001b[39m\n\u001b[0;32m      2\u001b[0m \u001b[38;5;124mMake a calendar event. Respond in JSON with\u001b[39m\n\u001b[0;32m      3\u001b[0m \u001b[38;5;124mthe event name, date, list of participants,\u001b[39m\n\u001b[0;32m      4\u001b[0m \u001b[38;5;124mand the address.\u001b[39m\n\u001b[0;32m      5\u001b[0m \u001b[38;5;124m\"\"\"\u001b[39m\n\u001b[0;32m      7\u001b[0m user_prompt \u001b[38;5;241m=\u001b[39m \u001b[38;5;124m'\u001b[39m\u001b[38;5;124mEvent description: \u001b[39m\u001b[38;5;124m'\u001b[39m \u001b[38;5;241m+\u001b[39m event_description\n\u001b[1;32m----> 9\u001b[0m event \u001b[38;5;241m=\u001b[39m generate(\n\u001b[0;32m     10\u001b[0m     CalendarEvent, \n\u001b[0;32m     11\u001b[0m     user_prompt, \n\u001b[0;32m     12\u001b[0m     system_prompt\u001b[38;5;241m=\u001b[39msystem_prompt\n\u001b[0;32m     13\u001b[0m )\n",
      "Cell \u001b[1;32mIn[15], line 10\u001b[0m, in \u001b[0;36mgenerate\u001b[1;34m(response_model, user_prompt, system_prompt, model, max_retries)\u001b[0m\n\u001b[0;32m      1\u001b[0m \u001b[38;5;28;01mdef\u001b[39;00m \u001b[38;5;21mgenerate\u001b[39m(\n\u001b[0;32m      2\u001b[0m     response_model, \n\u001b[0;32m      3\u001b[0m     user_prompt, \n\u001b[1;32m   (...)\u001b[0m\n\u001b[0;32m      8\u001b[0m     max_retries\u001b[38;5;241m=\u001b[39m\u001b[38;5;241m3\u001b[39m,\n\u001b[0;32m      9\u001b[0m ):\n\u001b[1;32m---> 10\u001b[0m     event \u001b[38;5;241m=\u001b[39m instructor_client\u001b[38;5;241m.\u001b[39mchat\u001b[38;5;241m.\u001b[39mcompletions\u001b[38;5;241m.\u001b[39mcreate(\n\u001b[0;32m     11\u001b[0m         model\u001b[38;5;241m=\u001b[39mmodel,\n\u001b[0;32m     12\u001b[0m         messages\u001b[38;5;241m=\u001b[39m[\n\u001b[0;32m     13\u001b[0m             {\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mrole\u001b[39m\u001b[38;5;124m\"\u001b[39m: \u001b[38;5;124m\"\u001b[39m\u001b[38;5;124msystem\u001b[39m\u001b[38;5;124m\"\u001b[39m, \u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mcontent\u001b[39m\u001b[38;5;124m\"\u001b[39m: system_prompt},\n\u001b[0;32m     14\u001b[0m             {\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mrole\u001b[39m\u001b[38;5;124m\"\u001b[39m: \u001b[38;5;124m\"\u001b[39m\u001b[38;5;124muser\u001b[39m\u001b[38;5;124m\"\u001b[39m, \u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mcontent\u001b[39m\u001b[38;5;124m\"\u001b[39m: user_prompt\n\u001b[0;32m     15\u001b[0m             },\n\u001b[0;32m     16\u001b[0m         ],\n\u001b[0;32m     17\u001b[0m         response_model\u001b[38;5;241m=\u001b[39mresponse_model,\n\u001b[0;32m     18\u001b[0m         max_retries\u001b[38;5;241m=\u001b[39mmax_retries\n\u001b[0;32m     19\u001b[0m     )\n\u001b[0;32m     21\u001b[0m     \u001b[38;5;28;01mreturn\u001b[39;00m event\n",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\instructor\\client.py:180\u001b[0m, in \u001b[0;36mInstructor.create\u001b[1;34m(self, response_model, messages, max_retries, validation_context, context, strict, **kwargs)\u001b[0m\n\u001b[0;32m    168\u001b[0m \u001b[38;5;28;01mdef\u001b[39;00m \u001b[38;5;21mcreate\u001b[39m(\n\u001b[0;32m    169\u001b[0m     \u001b[38;5;28mself\u001b[39m,\n\u001b[0;32m    170\u001b[0m     response_model: \u001b[38;5;28mtype\u001b[39m[T] \u001b[38;5;241m|\u001b[39m \u001b[38;5;28;01mNone\u001b[39;00m,\n\u001b[1;32m   (...)\u001b[0m\n\u001b[0;32m    176\u001b[0m     \u001b[38;5;241m*\u001b[39m\u001b[38;5;241m*\u001b[39mkwargs: Any,\n\u001b[0;32m    177\u001b[0m ) \u001b[38;5;241m-\u001b[39m\u001b[38;5;241m>\u001b[39m T \u001b[38;5;241m|\u001b[39m Any \u001b[38;5;241m|\u001b[39m Awaitable[T] \u001b[38;5;241m|\u001b[39m Awaitable[Any]:\n\u001b[0;32m    178\u001b[0m     kwargs \u001b[38;5;241m=\u001b[39m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39mhandle_kwargs(kwargs)\n\u001b[1;32m--> 180\u001b[0m     \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39mcreate_fn(\n\u001b[0;32m    181\u001b[0m         response_model\u001b[38;5;241m=\u001b[39mresponse_model,\n\u001b[0;32m    182\u001b[0m         messages\u001b[38;5;241m=\u001b[39mmessages,\n\u001b[0;32m    183\u001b[0m         max_retries\u001b[38;5;241m=\u001b[39mmax_retries,\n\u001b[0;32m    184\u001b[0m         validation_context\u001b[38;5;241m=\u001b[39mvalidation_context,\n\u001b[0;32m    185\u001b[0m         context\u001b[38;5;241m=\u001b[39mcontext,\n\u001b[0;32m    186\u001b[0m         strict\u001b[38;5;241m=\u001b[39mstrict,\n\u001b[0;32m    187\u001b[0m         hooks\u001b[38;5;241m=\u001b[39m\u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39mhooks,\n\u001b[0;32m    188\u001b[0m         \u001b[38;5;241m*\u001b[39m\u001b[38;5;241m*\u001b[39mkwargs,\n\u001b[0;32m    189\u001b[0m     )\n",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\instructor\\patch.py:193\u001b[0m, in \u001b[0;36mpatch.<locals>.new_create_sync\u001b[1;34m(response_model, validation_context, context, max_retries, strict, hooks, *args, **kwargs)\u001b[0m\n\u001b[0;32m    187\u001b[0m response_model, new_kwargs \u001b[38;5;241m=\u001b[39m handle_response_model(\n\u001b[0;32m    188\u001b[0m     response_model\u001b[38;5;241m=\u001b[39mresponse_model, mode\u001b[38;5;241m=\u001b[39mmode, \u001b[38;5;241m*\u001b[39m\u001b[38;5;241m*\u001b[39mkwargs\n\u001b[0;32m    189\u001b[0m )  \u001b[38;5;66;03m# type: ignore\u001b[39;00m\n\u001b[0;32m    191\u001b[0m new_kwargs \u001b[38;5;241m=\u001b[39m handle_templating(new_kwargs, mode\u001b[38;5;241m=\u001b[39mmode, context\u001b[38;5;241m=\u001b[39mcontext)\n\u001b[1;32m--> 193\u001b[0m response \u001b[38;5;241m=\u001b[39m retry_sync(\n\u001b[0;32m    194\u001b[0m     func\u001b[38;5;241m=\u001b[39mfunc,  \u001b[38;5;66;03m# type: ignore\u001b[39;00m\n\u001b[0;32m    195\u001b[0m     response_model\u001b[38;5;241m=\u001b[39mresponse_model,\n\u001b[0;32m    196\u001b[0m     context\u001b[38;5;241m=\u001b[39mcontext,\n\u001b[0;32m    197\u001b[0m     max_retries\u001b[38;5;241m=\u001b[39mmax_retries,\n\u001b[0;32m    198\u001b[0m     args\u001b[38;5;241m=\u001b[39margs,\n\u001b[0;32m    199\u001b[0m     hooks\u001b[38;5;241m=\u001b[39mhooks,\n\u001b[0;32m    200\u001b[0m     strict\u001b[38;5;241m=\u001b[39mstrict,\n\u001b[0;32m    201\u001b[0m     kwargs\u001b[38;5;241m=\u001b[39mnew_kwargs,\n\u001b[0;32m    202\u001b[0m     mode\u001b[38;5;241m=\u001b[39mmode,\n\u001b[0;32m    203\u001b[0m )\n\u001b[0;32m    204\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m response\n",
      "File \u001b[1;32m~\\AppData\\Roaming\\Python\\Python311\\site-packages\\instructor\\retry.py:194\u001b[0m, in \u001b[0;36mretry_sync\u001b[1;34m(func, response_model, args, kwargs, context, max_retries, strict, mode, hooks)\u001b[0m\n\u001b[0;32m    192\u001b[0m \u001b[38;5;28;01mexcept\u001b[39;00m RetryError \u001b[38;5;28;01mas\u001b[39;00m e:\n\u001b[0;32m    193\u001b[0m     logger\u001b[38;5;241m.\u001b[39mdebug(\u001b[38;5;124mf\u001b[39m\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mRetry error: \u001b[39m\u001b[38;5;132;01m{\u001b[39;00me\u001b[38;5;132;01m}\u001b[39;00m\u001b[38;5;124m\"\u001b[39m)\n\u001b[1;32m--> 194\u001b[0m     \u001b[38;5;28;01mraise\u001b[39;00m InstructorRetryException(\n\u001b[0;32m    195\u001b[0m         e\u001b[38;5;241m.\u001b[39mlast_attempt\u001b[38;5;241m.\u001b[39m_exception,\n\u001b[0;32m    196\u001b[0m         last_completion\u001b[38;5;241m=\u001b[39mresponse,\n\u001b[0;32m    197\u001b[0m         n_attempts\u001b[38;5;241m=\u001b[39mattempt\u001b[38;5;241m.\u001b[39mretry_state\u001b[38;5;241m.\u001b[39mattempt_number,\n\u001b[0;32m    198\u001b[0m         \u001b[38;5;66;03m#! deprecate messages soon\u001b[39;00m\n\u001b[0;32m    199\u001b[0m         messages\u001b[38;5;241m=\u001b[39mextract_messages(\n\u001b[0;32m    200\u001b[0m             kwargs\n\u001b[0;32m    201\u001b[0m         ),  \u001b[38;5;66;03m# Use the optimized function instead of nested lookups\u001b[39;00m\n\u001b[0;32m    202\u001b[0m         create_kwargs\u001b[38;5;241m=\u001b[39mkwargs,\n\u001b[0;32m    203\u001b[0m         total_usage\u001b[38;5;241m=\u001b[39mtotal_usage,\n\u001b[0;32m    204\u001b[0m     ) \u001b[38;5;28;01mfrom\u001b[39;00m \u001b[38;5;21;01me\u001b[39;00m\n",
      "\u001b[1;31mInstructorRetryException\u001b[0m: Instructor does not support multiple tool calls, use List[Model] instead"
     ]
    }
   ],
   "source": [
    "system_prompt = \"\"\"\n",
    "Make a calendar event. Respond in JSON with\n",
    "the event name, date, list of participants,\n",
    "and the address.\n",
    "\"\"\"\n",
    "\n",
    "user_prompt = 'Event description: ' + event_description\n",
    "\n",
    "event = generate(\n",
    "    CalendarEvent, \n",
    "    user_prompt, \n",
    "    system_prompt=system_prompt\n",
    ")"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "chat-bi",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.11.11"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
